package com.example.gaoyang.util;

import com.example.gaoyang.annotation.ExcelHeader;
import com.example.gaoyang.annotation.ExcelIgnore;
import com.example.gaoyang.annotation.ExportImage;
import lombok.extern.slf4j.Slf4j;
import org.apache.poi.ss.usermodel.*;
import org.apache.poi.ss.util.CellRangeAddress;
import org.apache.poi.xssf.usermodel.XSSFClientAnchor;
import org.apache.poi.xssf.usermodel.XSSFWorkbook;

import javax.imageio.ImageIO;
import javax.servlet.http.HttpServletResponse;
import java.awt.image.BufferedImage;
import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
import java.lang.reflect.Field;
import java.net.URLEncoder;
import java.nio.file.Files;
import java.nio.file.Paths;
import java.util.ArrayList;
import java.util.List;

@Slf4j
public class ExcelUtil {

    /**
     * 导出数据到Excel文件
     * @param list
     * @param filePath
     * @param <T>
     */
    public static <T> void exportToXlsxWithPath(List<T> list, String filePath) {
        // 创建工作簿
        Workbook workbook = new XSSFWorkbook();
        try {
            // 创建工作表
            Sheet sheet = workbook.createSheet("sheet1");
            // 获取实体类的所有字段
            Field[] fields = list.get(0).getClass().getDeclaredFields();
            // 创建表头
            Row headerRow = sheet.createRow(0);
            for (int i = 0; i < fields.length; i++) {
                Field field = fields[i];
                field.setAccessible(true);
                ExcelHeader excelHeader = field.getAnnotation(ExcelHeader.class);
                if (excelHeader != null) {
                    headerRow.createCell(i).setCellValue(excelHeader.value());
                } else {
                    headerRow.createCell(i).setCellValue(field.getName());
                }
            }
            // 填充数据
            for (int i = 0; i < list.size(); i++) {
                T item = list.get(i);
                Row dataRow = sheet.createRow(i + 1);
                for (int j = 0; j < fields.length; j++) {
                    Field field = fields[j];
                    field.setAccessible(true);
                    try {
                        Object value = field.get(item);
                        if (value != null) {
                            Cell cell = dataRow.createCell(j);
                            if (value instanceof Number) {
                                cell.setCellValue(((Number) value).doubleValue());
                            } else {
                                cell.setCellValue(String.valueOf(value));
                            }
                        }
                    } catch (IllegalAccessException e) {
                        log.error("获取字段值失败", e);
                    }
                }
            }
            // 写入文件
            FileOutputStream fileOut = new FileOutputStream(filePath);
            workbook.write(fileOut);
        } catch (Exception e) {
            log.error("导出数据到Excel文件失败", e);
        } finally {
            // 关闭工作簿
            try {
                workbook.close();
            } catch (IOException e) {
                log.error("关闭工作簿失败", e);
            }
        }
    }


    /**
     * 导出数据到Excel文件
     * @param list
     * @param <T>
     * @return
     * @throws IOException
     */
    public static <T> Workbook exportToXlsx(List<T> list) {
        // 创建工作簿
        Workbook workbook = new XSSFWorkbook();
        try {
            // 创建工作表
            Sheet sheet = workbook.createSheet("Data");
            // 获取实体类的所有字段
            Field[] fields = list.get(0).getClass().getDeclaredFields();
            // 过滤掉被 @ExcelIgnore 标记的字段
            List<Field> exportableFields = new ArrayList<>();
            for (Field field : fields) {
                if (field.getAnnotation(ExcelIgnore.class) == null) {
                    exportableFields.add(field);
                }
            }
            // 创建表头
            Row headerRow = sheet.createRow(0);
            for (int i = 0; i < exportableFields.size(); i++) {
                Field field = exportableFields.get(i);
                field.setAccessible(true);
                ExcelHeader excelHeader = field.getAnnotation(ExcelHeader.class);
                if (excelHeader != null) {
                    headerRow.createCell(i).setCellValue(excelHeader.value());
                } else {
                    headerRow.createCell(i).setCellValue(field.getName());
                }
            }
            // 填充数据
            for (int i = 0; i < list.size(); i++) {
                T item = list.get(i);
                Row dataRow = sheet.createRow(i + 1);
                for (int j = 0; j < exportableFields.size(); j++) {
                    Field field = exportableFields.get(j);
                    field.setAccessible(true);
                    try {
                        Object value = field.get(item);
                        if (value != null) {
                            Cell cell = dataRow.createCell(j);
                            if (value instanceof Number) {
                                cell.setCellValue(((Number) value).doubleValue());
                            } else {
                                cell.setCellValue(String.valueOf(value));
                            }
                        }
                    } catch (IllegalAccessException e) {
                        log.error("获取字段值失败", e);
                    }
                }
            }
        } catch (Exception e) {
            log.error("导出数据到Excel文件失败", e);
        }
        return workbook;
    }


    public static <T> Workbook exportToXlsxWithPictures(List<T> list) {
        // 创建工作簿
        Workbook workbook = new XSSFWorkbook();
        try {
            // 创建工作表
            Sheet sheet = workbook.createSheet("Data");
            // 获取实体类的所有字段
            Field[] fields = list.get(0).getClass().getDeclaredFields();
            // 创建表头
            Row headerRow = sheet.createRow(0);
            int pictureColumnIndex = -1;
            int maxPictureCount = 0;
            for (int i = 0; i < fields.length; i++) {
                Field field = fields[i];
                field.setAccessible(true);
                ExcelHeader excelHeader = field.getAnnotation(ExcelHeader.class);
                if (excelHeader != null) {
                    Cell cell = headerRow.createCell(i);
                    cell.setCellValue(excelHeader.value());
                    // 检查字段是否包含 @ExportImage 注解
                    ExportImage exportImage = field.getAnnotation(ExportImage.class);
                    if (exportImage != null) {
                        pictureColumnIndex = i;
                    }
                } else {
                    headerRow.createCell(i).setCellValue(field.getName());
                }
            }
            // 找到最长的图片列表长度
            for (T item : list) {
                for (Field field : fields) {
                    field.setAccessible(true);
                    ExportImage exportImage = field.getAnnotation(ExportImage.class);
                    if (exportImage != null) {
                        try {
                            List<String> imageUrls = (List<String>) field.get(item);
                            if (imageUrls != null) {
                                maxPictureCount = Math.max(maxPictureCount, imageUrls.size());
                            }
                        } catch (IllegalAccessException e) {
                            log.error("获取字段值失败", e);
                        }
                    }
                }
            }
            if (maxPictureCount > 1) {
                // 合并表头单元格
                if (pictureColumnIndex != -1) {
                    CellRangeAddress range = new CellRangeAddress(0, 0, pictureColumnIndex, pictureColumnIndex + maxPictureCount - 1);
                    sheet.addMergedRegion(range);
                    Cell cell = headerRow.getCell(pictureColumnIndex);
                    cell.setCellValue("图片");
                }
            }
            // 填充数据
            for (int i = 0; i < list.size(); i++) {
                T item = list.get(i);
                Row dataRow = sheet.createRow(i + 1);
                for (int j = 0; j < fields.length; j++) {
                    Field field = fields[j];
                    field.setAccessible(true);
                    try {
                        Object value = field.get(item);
                        if (value != null) {
                            Cell cell = dataRow.createCell(j);
                            // 检查字段是否包含 @ExportImage 注解
                            ExportImage exportImage = field.getAnnotation(ExportImage.class);
                            if (exportImage != null && value instanceof List) {
                                // 处理图片导出
                                List<String> imageUrls = (List<String>) value;
                                if (!imageUrls.isEmpty()) {
                                    // 获取绘图对象
                                    Drawing<?> drawing = sheet.createDrawingPatriarch();
                                    CreationHelper helper = workbook.getCreationHelper();
                                    for (int k = 0; k < imageUrls.size(); k++) {
                                        String imageUrl = imageUrls.get(k);
                                        // 读取图片
                                        BufferedImage img = ImageIO.read(new File(imageUrl));
                                        if (img == null) {
                                            log.error("图片加载失败: {}", imageUrl);
                                            continue;
                                        }
                                        byte[] imageBytes = Files.readAllBytes(Paths.get(imageUrl));
                                        int pictureIdx = workbook.addPicture(imageBytes, Workbook.PICTURE_TYPE_JPEG);
                                        // 创建锚点
                                        XSSFClientAnchor anchor = new XSSFClientAnchor();
                                        // 设置固定高度，例如100像素
                                        int fixedHeight = 50;
                                        // 计算宽度以保持比例
                                        int imgWidth = img.getWidth();
                                        int imgHeight = img.getHeight();
                                        double scale = (double) fixedHeight / imgHeight;
                                        int scaledWidth = (int) (imgWidth * scale);
                                        anchor.setCol1(pictureColumnIndex + k);
                                        anchor.setRow1(i + 1);
                                        anchor.setCol2(pictureColumnIndex + k + 1);
                                        anchor.setRow2(i + 2);
                                        anchor.setDx1(0);
                                        anchor.setDy1(0);
                                        anchor.setDx2(0);
                                        anchor.setDy2(0);
                                        // 设置图片大小
                                        anchor.setDx1(0);
                                        anchor.setDy1(0);
                                        anchor.setDx2((int) (scaledWidth * 1024 / sheet.getDefaultColumnWidth()));
                                        anchor.setDy2((int) (fixedHeight * 1024 / sheet.getDefaultRowHeight()));
                                        // 插入图片
                                        drawing.createPicture(anchor, pictureIdx);
                                        log.info("图片插入成功: {} [行{} 列{}]", imageUrl, i + 1, pictureColumnIndex + k);
                                        // 调整单元格宽度和高度
                                        sheet.setColumnWidth(pictureColumnIndex + k, (int) (scaledWidth * 1024 / sheet.getDefaultColumnWidth()));
                                        dataRow.setHeightInPoints(fixedHeight);
                                    }
                                }
                            } else if (value instanceof Number) {
                                cell.setCellValue(((Number) value).doubleValue());
                            } else {
                                cell.setCellValue(String.valueOf(value));
                            }
                        }
                    } catch (IllegalAccessException e) {
                        log.error("获取字段值失败", e);
                    } catch (IOException e) {
                        log.error("图片处理失败", e);
                    }
                }
            }
        } catch (Exception e) {
            log.error("导出数据到Excel文件失败", e);
        }
        return workbook;
    }



    /**
     * 发送响应方法
     *
     * @param response
     * @param fileName
     */
    public static void setResponseHeader(HttpServletResponse response, String fileName) {
        try {
            response.setContentType("application/octet-stream;charset=UTF-8");
            response.setHeader("Content-Disposition", "attachment;filename=" + URLEncoder.encode(fileName, "UTF-8"));
            response.addHeader("Pargam", "no-cache");
            response.addHeader("Cache-Control", "no-cache");
        } catch (Exception e) {
            log.error("发送响应头出错", e);
        }
    }
}
